// Multiple inherit

#include <iostream>
#include <cstring>
using namespace std;

class A {
public:
	A( ) { cout << "A" << endl; }
	~A( ) { cout << "A" << endl; }
	int m_a;
};

class B {
public:
	B( ) { cout << "B" << endl; }
	~B( ) { cout << "B" << endl; }
	int m_b;
};

class C {
public:
	C( ) { cout << "C" << endl; }
	~C( ) { cout << "C" << endl; }
	int m_c;
};


// Aggregation subclass.
class D : public A, public B, public C {
public:
	int m_d;
};

// designer
// ------------------------------------------------------------------
// user

int main( void ) { 
	D d;
	cout << "sizeof( d )  = " << sizeof( d ) << endl;

	D* pd = &d;
	cout << "Address of all : " << pd << endl;
	cout << "Address of A : " << &d.m_a << endl;
	cout << "Address of B : " << &d.m_b << endl;
	cout << "Address of C : " << &d.m_c << endl;
	cout << "Address of D : " << &d.m_d << endl;

	cout << "--------------   Implicit conversion   -------------------" << endl;
	A* pa = pd;
	cout << "D* pd ---->>> A* pa : " << pa << endl;
	B* pb = pd;
	cout << "D* pd ---->>> A* pb : " << pb << endl;
	C* pc = pd;
	cout << "D* pd ---->>> A* pc : " << pc << endl;

	cout << "--------------       static_cast        ------------------" << endl;
	D* p1 = static_cast<D*>(pa);
	cout << "A* pa --->>> D* p1 : " << p1 <<  endl;
	D* p2 = static_cast<D*>(pb);
	cout << "A* pa --->>> D* p2 : " << p2 <<  endl;
	D* p3 = static_cast<D*>(pc);
	cout << "A* pa --->>> D* p3 : " << p3 <<  endl;

	// The conversion will not change the address.
	cout << "--------------   reinterpret_cast   -------------------" << endl;
	pa = reinterpret_cast<A*>(pd);
	cout << "D* pd ---->>> A* pa : " << pa << endl;
	pb = reinterpret_cast<B*>(pd);
	cout << "D* pd ---->>> A* pb : " << pb << endl;
	pc = reinterpret_cast<C*>(pd);
	cout << "D* pd ---->>> A* pc : " << pc << endl;

	return 0;
}

